Skip to content

release: v1.0.0 배포를 위한 develop 병합#146

Merged
yousung1020 merged 150 commits intomainfrom
develop
Apr 8, 2026
Merged

release: v1.0.0 배포를 위한 develop 병합#146
yousung1020 merged 150 commits intomainfrom
develop

Conversation

@yousung1020
Copy link
Copy Markdown
Contributor

  • 실제 서비스 배포용 릴리즈 PR

yousung1020 and others added 30 commits January 6, 2026 00:14
* infra: CI/CD 파이프라인 초기 구축 완료

* fix: Deploy to EC2 단계에서 오류 발생 내역 수정 후 재테스트 예정

* infra: 테스트 완료 후, develop 브랜치에서 변경이 감지될 경우 Github Actions가 동작하게끔 변경

* refactor: deploy.yml 단순화

* refactor: deploy.yml 단순화

* refactor: deploy.yml 단순화 및 오류 수정

* fix: develop 브랜치에 변경 사항 발생시 자동 재배포 하도록 수정
* feat: Route 및 RouteDetail 엔티티 추가

* feat: [이슈#7] 경로 엔티티 관련 기능 구현 완료

* fit: pr 리뷰 반영
- settings 도메인 알림 구조 개편
- 일정 알림 / 출발 알림 분리 구조 적용
- ReminderTime 엔티티 구조 정리
- 캘린더 타입 설정 로직 정비
- Settings API Swagger 문서화 완료
dmlwjds2 and others added 28 commits February 12, 2026 01:11
* feat: RouteDetail 상세 정보 JSON 저장

* feat: 일정 필드 추가
* feat & refactor: Nginx 리버스 프록시 도입 및 보안 강화

* fix: 테스트 완료 후 디벨롭에 배포되게끔 수정

* refactor: 리뷰 반영
* feat: ssl 인증서 발급을 통한 https 통신 구현

* fix: 임시 실행을 위한 443 포트 설정 주석

* fix: 주석 제거

* fix: health 체크 예외 처리

* fix: 배포관련 문제 해결

* fix: 배포관련 문제 수정

* fix: 배포관련 문제 수정

* fix: 개발 브랜치에 배포 트리거 제거

* refactor: 리뷰 반영
* refactor: ScheduleConverter로 통일

* refactor: 반복 일정 코드 삭제

- 경로일정 Id 음수Id로 변경
- 반복 일정 코드 삭제
- 일반 일정 관리 x -> 불필요한 필드 삭제

* refactor: RouteDetail 저장 방식 변경 (JSON -> 개별 필드)

* refactor: 리뷰 반영 수정

* refactor: ScheduleConverter static화

* refactor: 1:1 연관관계 피드백 반영
* refactor: calendarType 제거 및 calendarId(Long) 기반으로 온보딩/세팅 로직 변경

* refactor(schedule): 경로 삭제 API 파라미터 순서 오류 및 route 조회 로직 수정

* refactor(schedule): orphanRemoval 연결 route 삭제 로직 개선
* feat: 실시간 지하철 도착 정보 조회 기능 구현

* feat: 컨트롤러 구현

* refactor: 리뷰 반영

* fix: deploy.yml에 .env 파일 내용 추가
* feat: 버스 실시간 도착 정보 조회를 위한 출발 정류장 조회 API 구현

* feat: 버스 실시간 도착 정보 조회를 위한 출발 정류장 조회 API 구현
* fix: 실시간 지하철 데이터 필드에서 다음역 이름 정보도 포함하여 응답

* refactor: 리뷰 반영
* feat: 일정 자동 삭제 로직 추가

* 리뷰 반영 수정

* refactor: 벌크 삭제로 변경
* refactor: 대중교통 경로 탐색 시 지하철 상/하행 판별 로직 리팩토링리뷰 반영

* refactor: 리뷰 반영
Copy link
Copy Markdown

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request initializes the Pace server backend, implementing core features for authentication, member management, scheduling, and transit data integration alongside a Docker-based deployment setup. The review identifies several critical build configuration errors, including non-existent versions for Spring Boot and related libraries, and a significant security vulnerability regarding unauthorized schedule access. Furthermore, the feedback highlights necessary corrections for JPQL bulk delete syntax, potential null pointer exceptions in member processing, and opportunities to improve performance and maintainability through better collection usage and refactoring of hardcoded values.

Comment on lines +47 to +48
@Query("DELETE FROM Route r WHERE r.schedule.endDate < :date")
void deleteRoutesByScheduleEndDateBefore(@Param("date") LocalDate date);
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

critical

JPQL의 DELETE 문에서는 WHERE 절에서 직접적인 연관관계 경로(e.g., r.schedule.endDate)를 사용할 수 없습니다. 서브쿼리를 사용하여 삭제할 대상을 찾아야 합니다. 이는 성능을 위해 @Modifying@Query를 사용하고 자식 엔티티를 먼저 삭제하도록 하는 프로젝트 규칙과도 일치합니다.

Suggested change
@Query("DELETE FROM Route r WHERE r.schedule.endDate < :date")
void deleteRoutesByScheduleEndDateBefore(@Param("date") LocalDate date);
@Query("DELETE FROM Route r WHERE r.schedule IN (SELECT s FROM Schedule s WHERE s.endDate < :date)")
void deleteRoutesByScheduleEndDateBefore(@Param("date") LocalDate date);
References
  1. 성능 향상을 위해 @Modifying@query를 사용한 벌크 삭제를 권장하며, 연관관계가 있는 경우 자식 엔티티를 부모보다 먼저 삭제해야 합니다.

Comment on lines +38 to +39
@Query("select s from Schedule s join fetch s.member where s.id in :ids")
List<Schedule> findAllWithMemberByIdIn(@Param("ids") List<Long> ids, @Param("memberId") Long memberId);
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

security-critical critical

이 쿼리는 memberId를 파라미터로 받지만, 실제 쿼리문에서는 사용하지 않고 있습니다. 이로 인해 다른 사용자가 scheduleId만 알면 타인의 일정을 삭제할 수 있는 심각한 보안 취약점이 발생합니다. WHERE 절에 s.member.id = :memberId 조건을 반드시 추가해야 합니다.

Suggested change
@Query("select s from Schedule s join fetch s.member where s.id in :ids")
List<Schedule> findAllWithMemberByIdIn(@Param("ids") List<Long> ids, @Param("memberId") Long memberId);
@Query("select s from Schedule s join fetch s.member where s.id in :ids and s.member.id = :memberId")
List<Schedule> findAllWithMemberByIdIn(@Param("ids") List<Long> ids, @Param("memberId") Long memberId);

testRuntimeOnly 'com.h2database:h2'

// Swagger UI
implementation("org.springdoc:springdoc-openapi-starter-webmvc-ui:3.0.1")
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

critical

springdoc-openapi-starter-webmvc-ui3.0.1 버전은 존재하지 않습니다. Spring Boot 3.x 버전을 사용하신다면 2.x 버전대를 사용해야 합니다. 예를 들어, 2.5.0으로 수정해야 합니다.

    implementation("org.springdoc:springdoc-openapi-starter-webmvc-ui:2.5.0")

Comment on lines +64 to +68
implementation "io.github.openfeign.querydsl:querydsl-jpa:7.0"
implementation "io.github.openfeign.querydsl:querydsl-core:7.0"
annotationProcessor "io.github.openfeign.querydsl:querydsl-apt:7.0:jpa"
annotationProcessor "jakarta.persistence:jakarta.persistence-api"
annotationProcessor "jakarta.annotation:jakarta.annotation-api"
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

critical

QueryDSL 의존성 정보가 잘못되었습니다. io.github.openfeign.querydsl 그룹의 7.0 버전은 존재하지 않습니다. 공식 QueryDSL 의존성(com.querydsl)을 사용하고 Spring Boot 3.x에 맞는 버전을 사용해야 합니다.

    // QueryDSL
    implementation 'com.querydsl:querydsl-jpa:5.1.0:jakarta'
    annotationProcessor 'com.querydsl:querydsl-apt:5.1.0:jakarta'
    annotationProcessor 'jakarta.persistence:jakarta.persistence-api'
    annotationProcessor 'jakarta.annotation:jakarta.annotation-api'

@@ -1 +1,6 @@
pluginManagement {
plugins {
id 'org.jetbrains.kotlin.jvm' version '2.1.21'
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

critical

Kotlin JVM 플러그인 버전 2.1.21은 존재하지 않는 버전입니다. 올바른 버전으로 수정해야 합니다. 또한, 프로젝트가 Java로만 구성되어 있다면 이 플러그인은 불필요할 수 있습니다.

        id 'org.jetbrains.kotlin.jvm' version '1.9.23'

Comment on lines +5 to +8
import org.springframework.context.annotation.Bean;
import org.springframework.data.jpa.repository.config.EnableJpaAuditing;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.web.reactive.function.client.WebClient;
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

사용하지 않는 import 문(Bean, WebClient)이 있습니다. 코드를 깔끔하게 유지하기 위해 제거하는 것이 좋습니다.

Comment on lines +78 to +79
List<String> targetPlaceIdList = targetGroup.getSavedPlaceList().stream()
.map(SavedPlace::getPlaceId).toList();
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

targetPlaceIdListList 대신 Set으로 만들면 contains 연산의 성능을 O(N)에서 O(1)로 향상시킬 수 있습니다. 이동할 장소의 수가 많아질 경우 성능에 영향을 줄 수 있습니다. targetPlaceIdList.contains를 사용하는 반복문 내부의 성능 개선을 위해 Set으로 변경하는 것을 권장합니다.

Suggested change
List<String> targetPlaceIdList = targetGroup.getSavedPlaceList().stream()
.map(SavedPlace::getPlaceId).toList();
java.util.Set<String> targetPlaceIdSet = targetGroup.getSavedPlaceList().stream()
.map(SavedPlace::getPlaceId).collect(java.util.stream.Collectors.toSet());

id 'java'
id 'org.springframework.boot' version '4.0.1'
id 'io.spring.dependency-management' version '1.1.7'
id 'org.jetbrains.kotlin.jvm'
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

프로젝트가 Java로 작성된 것으로 보이는데, Kotlin 관련 플러그인(org.jetbrains.kotlin.jvm)과 의존성(kotlin-stdlib-jdk8)이 추가되었습니다. 만약 Kotlin을 사용하지 않는다면, 불필요한 의존성이므로 제거하는 것이 좋습니다.

Comment on lines +143 to +165
String mappedLineName = switch (apiSubwayId) {
case "1001" -> "1호선";
case "1002" -> "2호선";
case "1003" -> "3호선";
case "1004" -> "4호선";
case "1005" -> "5호선";
case "1006" -> "6호선";
case "1007" -> "7호선";
case "1008" -> "8호선";
case "1009" -> "9호선";
case "1061" -> "중앙선";
case "1063" -> "경의중앙선";
case "1065" -> "공항철도";
case "1067" -> "경춘선";
case "1075" -> "수인분당선";
case "1077" -> "신분당선";
case "1092" -> "우이신설선";
case "1093" -> "서해선";
case "1081" -> "경강선";
case "1032" -> "GTX-A";
default -> "";
};

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

지하철 노선 ID와 이름 매핑이 하드코딩되어 있어 유지보수가 어렵습니다. 새로운 노선이 추가될 때마다 코드를 수정해야 합니다. 이 매핑 정보를 Enum이나 static final Map으로 분리하여 관리하는 것이 더 좋습니다.

# Spring Boot
pace-app:
# Docker Hub의 Dockerfile을 기반으로 이미지를 빌드
image: shootingstar1020/pace-project:latest
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

latest 태그를 사용하는 것은 이미지 버전이 변경될 때 예기치 않은 동작을 유발할 수 있어 프로덕션 환경에서는 권장되지 않습니다. 재현 가능하고 안정적인 배포를 위해 특정 버전 태그(예: v1.0.0 또는 git commit hash)를 사용하시는 것을 고려해 보세요.

    image: shootingstar1020/pace-project:v1.0.0

@yousung1020 yousung1020 merged commit 6aa2120 into main Apr 8, 2026
1 check passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants